/**
代理模式（Proxy Pattern）

意图：为其他对象提供一种代理以控制对这个对象的访问。
主要解决：在直接访问对象时带来的问题，比如说：要访问的对象在远程的机器上。在面向对象系统中，有些对象由于某些原因（比如对象创建开销很大，或者某些操作需要安全控制，或者需要进程外的访问），直接访问会给使用者或者系统结构带来很多麻烦，我们可以在访问此对象时加上一个对此对象的访问层。
何时使用：想在访问一个类时做一些控制。
如何解决：增加中间层。
*/
main(List<String> args) {
  Image image = new ProxyImage("dart_logo.png");

  // 图像将从磁盘加载
  image.display();
  // 图像不需要从磁盘加载
  image.display();
}

//////////////////////////////////////////////////////////////////

///
/// 创建一个接口
///
abstract class Image {
  void display();
}

///
/// 创建实现接口的实体类
///
class RealImage implements Image {
  String fileName;

  RealImage(this.fileName) {
    loadFromDisk(fileName);
  }

  @override
  void display() {
    print("Displaying $fileName");
  }

  void loadFromDisk(String fileName) {
    print("Loading $fileName");
  }
}

class ProxyImage implements Image {
  RealImage realImage;
  String fileName;

  ProxyImage(this.fileName);

  @override
  void display() {
    if (realImage == null) {
      realImage = RealImage(fileName);
    }
    realImage.display();
  }
}
